;; host/function.scm - (c) rohan drape, 2001-2005

(module 
 function mzscheme

;; Aliases

(define function? procedure?)
(define function-arity procedure-arity)

;; Must provide 'function-name' to evaluate to the symbol that names
;; the function `p', or to '#f' if the name cannot be acquired.

(define (function-name p)
  (if (function? p)
      (object-name p)
      (error "function-name: not a function" p)))

;; Must provide 'function-of-no-arguments?' to evaluates to '#t' iff
;; `p' is a function of no arguments.

(define (function-of-no-arguments? p)
  (and (function? p)
       (let ((a (function-arity p)))
	 (and (integer? a)
	      (= a 0)))))

;; Must provide 'thunk?' as a synonym for
;; 'function-of-no-arguments?'.

(define thunk? function-of-no-arguments?)

;; Must provide 'function-arity-required' to evaluates to the
;; required number of arguments to a function.

(define (function-arity-required p)
  (let ((a (function-arity p)))
    (cond ((integer? a) a)
	  ((list? a) (apply min a))
	  (else (arity-at-least-value a)))))

;; Must provide 'function-arity-optional?' predicate to determine if
;; a function allows optional arguments.

(define (function-arity-optional? p)
  (let ((a (function-arity p)))
    (if (integer? a) #f #t)))

;;

(define (function-of-arity? p n)
  (and (function? p)
       (= (function-arity-required p) n)))

(define (unary-function? p)   (function-of-arity? p 1))
(define (binary-function? p)  (function-of-arity? p 2))
(define (ternary-function? p) (function-of-arity? p 3))

(define (nary-function? p)
  (and (function? p)
       (function-arity-optional? p)))

(provide (all-defined)))
